package controlador.comer;

//

import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Date;
import java.util.Iterator;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;
import modelo.*;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.collection.PersistentList;
import util.HibernateUtil;
import util.NTupla;
import util.SwingPanel;
import util.Tupla;
import vista.comer.pantallaRegistrarEmpresaCliente;
import vista.comer.pantallaRegistrarNuevaPlanta;
import vista.interfaces.IPantallaPedidoABM;

//
//  Generated by StarUML(tm) Java Add-In
//
//  @ Project : Proyecto2010_Requerimientos-iuga
//  @ File Name : GestorABMPedido.java
//  @ Date : 14/06/2010
//  @ Author : Iuga
//
//




public class GestorABMPedido {
    //private pantallaRegistrarPedido pantalla;
    private IPantallaPedidoABM pantalla;

    private String nombre;
    private String descripcion;
    private EmpresaCliente empresa;
    private Planta planta;
    private Date fechaInicio;
    private Date fechaFin;
    private Date fechaAceptacion;
    private Date fechaRegistro;
    private double montoMaximo;
    private FormaDePago formaDePago;
    private String plazoEntrega;
    private String lugarEntrega;
//    private Date fechaLEP;
//    private Date fechaLVP;
    private String pliegoObra;
//    private String planosObra;

    private PedidoObra pedido;
    private ArrayList<ContactoResponsable> contactos;
/*
    public GestorABMPedido(pantallaRegistrarPedido pantalla)
    {
        this.pantalla = pantalla;
    }
*/
    public GestorABMPedido(IPantallaPedidoABM pantalla)
    {
        this.pantalla = pantalla;
        contactos = new ArrayList<ContactoResponsable>();

    }

    public GestorABMPedido(IPantallaPedidoABM aThis, int id) {
        this.pantalla = aThis;
        try
        {
            HibernateUtil.beginTransaction();
            this.pedido = (PedidoObra) HibernateUtil.getSessionFactory().openSession().load(PedidoObra.class, id);
            HibernateUtil.commitTransaction();
        }
        catch(Exception ex)
        {
            HibernateUtil.rollbackTransaction();
        }
    }

    public void nombreObra(String nombre)
    {
        this.nombre = nombre;
    }

    public void descripcionObra(String descripcion)
    {
        this.descripcion = descripcion;
    }

    public void seleccionEmpresaCliente() {

    }

    public void buscarPlantas() {

    }

    public void mostrarPlantasEmpresaSeleccionada() {

    }

    public void seleccionPlanta(Tupla p) {
        try{
            SessionFactory sf = HibernateUtil.getSessionFactory();
            Session sesion = sf.openSession();
            HibernateUtil.beginTransaction();
            this.planta = (Planta)sesion.load(Planta.class, p.getId());
            HibernateUtil.commitTransaction();
        }catch(Exception e)
        {
            System.out.println("ERROR:"+e.getMessage()+"|");
            HibernateUtil.rollbackTransaction();
            e.printStackTrace();
        }
    }

    public void fechaInicioYFin(Date fechaInicio, Date fechaFin)
    {
        this.fechaInicio = fechaInicio;
        this.fechaFin = fechaFin;
    }

    public void montoMaximo(double monto)
    {
        this.montoMaximo = monto;
    }

    public void formaDePago(Tupla f){
        try{
            SessionFactory sf = HibernateUtil.getSessionFactory();
            Session sesion = sf.openSession();
            HibernateUtil.beginTransaction();
            this.formaDePago = (FormaDePago)sesion.load(FormaDePago.class, f.getId());
            HibernateUtil.commitTransaction();
        }catch(Exception e)
        {
            System.out.println("ERROR:"+e.getMessage()+"|");
            HibernateUtil.rollbackTransaction();
            e.printStackTrace();
        }
    }

//    public void fechaLEP(Date fechaLEP) {
//
//        this.fechaLEP = fechaLEP;
//
//    }

//    public void fechaLVP(Date fechaLVP) {
//
//        this.fechaLVP = fechaLVP;
//
//    }

//    public void pliegoObra(String pliego) {
//
//        this.pliegoObra = pliego;
//
//    }
//
//    public void planosObra(String planos) {
//
//        this.planosObra = planos;
//
//    }

    @Deprecated
    public int generarNumeroPedido()
    {
        SessionFactory sf = HibernateUtil.getSessionFactory();
        Session sesion = sf.openSession();
        sesion.beginTransaction();
        int mayorLegajo=0;
        try{
            Object ob =sesion.createQuery("Select MAX(id) from PedidoObra").uniqueResult();
            if(ob!=null)
            {mayorLegajo=(Integer)ob;}
            else{mayorLegajo=0;}
            sesion.getTransaction().commit();
        }
        catch(Exception e){
          System.out.println("ERROR:"+e.getMessage()+"|");
            e.printStackTrace();
        }
        return (mayorLegajo+1);
    }


    /**
     * Toma la confirmacion del registro y empieza con el kilombo para
     * agregar un nuevo pedido
     */
    public int confirmacionRegistro(int id) {

        return crearPedidoObra(id);

    }

    private int crearPedidoObra(int id) {
        PedidoObra nuevo=null;
        if(id>0)
        {
            try
            {
                HibernateUtil.beginTransaction();
                nuevo = (PedidoObra)HibernateUtil.getSession().load(PedidoObra.class, id);
                HibernateUtil.commitTransaction();
            }
            catch(Exception ex)
            {
                HibernateUtil.rollbackTransaction();
            }
        }
        else
        {
            nuevo = new PedidoObra();
        }
        nuevo.setNombre(nombre);
        nuevo.setDescripcion(descripcion);
        nuevo.setPlanta(planta);
        nuevo.setFechaDeRegistro(new Date());
        nuevo.setFechaFin(fechaFin);
        nuevo.setFechaInicio(fechaInicio);
        nuevo.setPresupuestoMaximo(montoMaximo);
        nuevo.setFormaPago(formaDePago);
        nuevo.setPliego(pliegoObra);
//        nuevo.setContactos(contactos);
        nuevo.getContactos().clear();

        generarNumeroPedido();           // AL PEDO
        buscarUltimoNumeroPedidoObra();  // AL PEDO

        try{
            HibernateUtil.beginTransaction();
            Iterator it = contactos.iterator();
            while(it.hasNext()){
                ContactoResponsable cr = (ContactoResponsable)it.next();
                Iterator<Telefono> itTelefonos = cr.getTelefonos().iterator();
                while(itTelefonos.hasNext())
                {
                    Telefono telefono = itTelefonos.next();
                    HibernateUtil.getSession().saveOrUpdate(telefono);
                }
                nuevo.getContactos().add(cr);
                HibernateUtil.getSession().saveOrUpdate(cr);
            }
            HibernateUtil.getSession().saveOrUpdate(nuevo);
            HibernateUtil.commitTransaction();
        }catch(Exception e)
        {
            System.out.println("ERROR:"+e.getMessage()+"|");
            HibernateUtil.rollbackTransaction();
            e.printStackTrace();
        }
        return nuevo.getId();
    }

    private void crearPlanificacion()
    {

    }

    private void buscarUltimoNumeroPedidoObra() {

        // Deberia buscarlo, pero hibernate se encarga solo de ésto y
        // es transparente a nosotros =)

    }

    public void finCU() {

    }

    public void llamarCURegistrarNuevaEmpresaCliente() {
        pantallaRegistrarEmpresaCliente np = new pantallaRegistrarEmpresaCliente(this);
        SwingPanel.getInstance().addWindow(np);
        np.setVisible(true);
    }

    public void recargarComboBox() {
        this.pantalla.mostrarEmpresasCliente();
    }

    public ArrayList<Tupla> mostrarEmpresasCliente()
    {
        ArrayList<Tupla> tuplas = new ArrayList<Tupla>();
        SessionFactory sf = HibernateUtil.getSessionFactory();
        Session sesion = sf.openSession();

        sesion.beginTransaction();
        Iterator iter = sesion.createQuery("from EmpresaCliente ec order by ec.razonSocial").iterate();
        Tupla tupla=null;
        while ( iter.hasNext() )
        {
            EmpresaCliente ec = (EmpresaCliente)iter.next();
            tupla = new Tupla(ec.getId(),ec.getRazonSocial());
            tuplas.add(tupla);
        }
        return tuplas;
    }

    public ArrayList<Tupla> mostrarPlantasEmpresaCliente(int id) {
        ArrayList<Tupla> tuplas = new ArrayList<Tupla>();
        SessionFactory sf = HibernateUtil.getSessionFactory();
        Session sesion = sf.openSession();
        
        try
        {
            HibernateUtil.beginTransaction();
            EmpresaCliente ec = (EmpresaCliente)sesion.load(EmpresaCliente.class, id);
            //ArrayList<Planta> plantas = (ArrayList<Planta>)ec.getPlantas();
            PersistentList plantas = (PersistentList) ec.getPlantas();
            Iterator iter = plantas.iterator();
            while ( iter.hasNext() )
            {
                Planta pl = (Planta)iter.next();
                Tupla tupla = new Tupla(pl.getId(),pl.getRazonSocial());
                tuplas.add(tupla);
            }
            HibernateUtil.commitTransaction();
        }
        catch(Exception ex)
        {
            HibernateUtil.rollbackTransaction();
        }
        return tuplas;
    }

    public ArrayList<Tupla> mostrarFormasDePago() {
        ArrayList<Tupla> tuplas = new ArrayList<Tupla>();
        SessionFactory sf = HibernateUtil.getSessionFactory();
        Session sesion = sf.openSession();

        sesion.beginTransaction();
        Iterator iter = sesion.createQuery("from FormaDePago fp order by fp.nombre").iterate();
        Tupla tupla=null;
        while ( iter.hasNext() )
        {
            FormaDePago fp = (FormaDePago)iter.next();
            tupla = new Tupla(fp.getId(),fp.getNombre());
            tuplas.add(tupla);
        }
        return tuplas;
    }

    public ArrayList<Tupla> mostrarRoles() {
        ArrayList<Tupla> tuplas = new ArrayList<Tupla>();
        SessionFactory sf = HibernateUtil.getSessionFactory();
        Session sesion = sf.openSession();

        sesion.beginTransaction();
        Iterator iter = sesion.createQuery("from RolContactoResponsable rcr order by rcr.nombre").iterate();
        Tupla tupla=null;
        while ( iter.hasNext() )
        {
            RolContactoResponsable rcr = (RolContactoResponsable)iter.next();
            tupla = new Tupla(rcr.getId(),rcr.getNombre());
            tuplas.add(tupla);
        }
        return tuplas;
    }

    public ArrayList<Tupla> mostrarTiposTelefono() {
        ArrayList<Tupla> tuplas = new ArrayList<Tupla>();
        SessionFactory sf = HibernateUtil.getSessionFactory();
        Session sesion = sf.openSession();

        sesion.beginTransaction();
        Iterator iter = sesion.createQuery("from TipoTelefono tt order by tt.nombre").iterate();
        Tupla tupla=null;
        while ( iter.hasNext() )
        {
            TipoTelefono tt = (TipoTelefono)iter.next();
            tupla = new Tupla(tt.getId(),tt.getNombre());
            tuplas.add(tupla);
        }
        return tuplas;
    }

    public void llamarCURegistrarNuevaPlanta(Tupla empresa) {
        pantallaRegistrarNuevaPlanta np = new pantallaRegistrarNuevaPlanta(this,empresa);
        SwingPanel.getInstance().addWindow(np);
        np.setVisible(true);
    }

    public void setNuevaPlanta(int id) {
        this.pantalla.mostrarPlantasEmpresaCliente();
    }

 /***
  * De aquí en adelante se programan los metodos para los ABMs
  */
    public int buscarEmpresaCliente() {
        EmpresaCliente empresaCliente=null;
        try{
            HibernateUtil.beginTransaction();
            BigDecimal idEC = (BigDecimal)HibernateUtil.getSession().createSQLQuery("select ID_EMPRESA from PLANTA where ID_PLANTA="+pedido.getPlanta().getId()).uniqueResult();
            empresaCliente = (EmpresaCliente)HibernateUtil.getSession().load(EmpresaCliente.class,idEC.intValue());
            HibernateUtil.commitTransaction();
        }
        catch(Exception e){
            System.out.println("ERROR:"+e.getMessage()+"|");
            HibernateUtil.rollbackTransaction();
            e.printStackTrace();
       }
        return empresaCliente.getId();
    }

    public int getIdPedido(){
        return pedido.getId();
    }

    public String getNombrePedido(){
        if (pedido != null)
            return pedido.getNombre();
        else
            return "";
    }

    public String getDescripcionPedido(){
        if (pedido != null)
            return pedido.getDescripcion();
        else
            return "";
    }

    public int getIdEmpresaClientePedido(){
        Session sesion = HibernateUtil.getSessionFactory().openSession();
        Iterator itEmpresa = sesion.createQuery("from EmpresaCliente").iterate();
        EmpresaCliente ec = null;
        while(itEmpresa.hasNext()){
            ec = (EmpresaCliente)itEmpresa.next();
            if(ec.esMiPlanta(pedido.getPlanta().getId()))
                break;
        }
        if(ec !=null)
            return ec.getId();
        return -1;
    }

    public int getIdPlantaPedido(){
        if (pedido != null)
            return pedido.getId();
        else
            return -1;
    }

    public Date getFechaInicioPedido(){
        if (pedido != null)
            return pedido.getFechaInicio();
        else
            return null;
    }

    public Date getFechaFinPedido(){
        if (pedido != null)
            return pedido.getFechaFin();
        else
            return null;
    }

//    public String getMontoPedido(){
//        if (pedido != null)
//            return String.valueOf(pedido.getMonto());
//        else
//            return "";
//    }
//
//    public Date getFechaLEPPedido(){
//        if (pedido != null)
//            return pedido.getFechaLimiteEntregaPresupuesto();
//        else
//            return null;
//    }
//
//    public Date getFechaLVPPedido(){
//        if (pedido != null)
//            return pedido.getFechaLimiteValidezPresupuesto();
//        else
//            return null;
//    }

//    public String getPliegoPedido(){
//        if (pedido != null)
//            return pedido.getPliego();
//        else
//            return "";
//    }

//    public String getPlanosPedido(){
//        if (pedido != null)
//            return pedido.getPlanos();
//        else
//            return "";
//    }

//    public void contactoResponsable(int id_cr)
//    {
//        SessionFactory sf = HibernateUtil.getSessionFactory();
//        Session sesion = sf.openSession();
//        this.contacto = (ContactoResponsable)sesion.get(ContactoResponsable.class,id_cr);
//    }

    public void seleccionPedido(int idPedido) {
        this.buscarDatosPedido(idPedido);
        this.pantalla.setNumeroPedido(String.valueOf(this.pedido.getId()));
        this.pantalla.setNombreObra(this.pedido.getNombre());
        this.pantalla.setDescripcionObra(this.pedido.getDescripcion());
        int idPlanta = this.pedido.getPlanta().getId();
        try {
            Iterator itEmpresas = HibernateUtil.getSession().createQuery("from EmpresaCliente").iterate();
            EmpresaCliente ec = null;
            while(itEmpresas.hasNext()){
                ec = (EmpresaCliente)itEmpresas.next();
                if(ec.esMiPlanta(idPlanta)){
                    this.pantalla.setEmpresaCliente(ec.getId());
                    break;
                }
            }
        } catch (Exception ex) {
            System.out.println("ERROR:"+ex.getMessage()+"|");
            ex.printStackTrace();
        }
        this.pantalla.setPlanta(this.pedido.getPlanta().getId());
        this.pantalla.setFechaInicio(this.pedido.getFechaInicio());
        this.pantalla.setFechaFin(this.pedido.getFechaFin());
        this.pantalla.setFormaDePago(this.pedido.getFormaPago().getId());
        this.pantalla.setMontoPedido(String.valueOf(this.pedido.getPresupuestoMaximo()));
        this.contactos =  new ArrayList(pedido.getContactos());
        this.pantalla.actualizarListaContactosResponsables();
        
        // Esto debe ir al final para que se deshabiliten todos los campos cuando
        // el pedido está cancelado
        this.pantalla.setEstadoPedidoObra(this.pedido.getEstado());
        
        this.pantalla.setPliegosPedido(this.pedido.getPliego());
    }

    private void buscarDatosPedido(int idPedido){
        try{
            HibernateUtil.beginTransaction();
            this.pedido = (PedidoObra)HibernateUtil.getSession().load(PedidoObra.class, idPedido);
            HibernateUtil.commitTransaction();
        }
        catch(Exception e){
            System.out.println("ERROR:"+e.getMessage()+"|");
            HibernateUtil.rollbackTransaction();
            e.printStackTrace();
        }
    }

    /**
     * El Cancelar Pedido Tiene que Dar de Baja en una Transaccion:
     * - Pedido de Obra
     * - Todas las Cotizaciones asociadas (si las tiene)
     * - La planificacion (si la tiene)
     * - La Ejecición (si la tiene)
     * @param id
     * @return 
     */
    public boolean cancelarPedido(int id) {
        try{
            HibernateUtil.beginTransaction();
            this.pedido = (PedidoObra)HibernateUtil.getSession().load(PedidoObra.class, id);
            this.pedido.setEstadoCancelado();
            
            darDeBajaCotizaciones();
            darDeBajaPlanificacion();
            darDeBajaEjecucion();
            
            HibernateUtil.getSession().update(this.pedido);
            if(this.pedido.getCotizaciones()!=null){
                for (int i = 0; i < this.pedido.getCotizaciones().size(); i++) {
                    Cotizacion cot = this.pedido.getCotizaciones().get(i);
                    HibernateUtil.getSession().update(cot);
                }
            }
            if(this.pedido.getPlanificacion()!=null){
                HibernateUtil.getSession().update(this.pedido.getPlanificacion());
            }
            
            if(this.pedido.getEjecucion()!=null){
                HibernateUtil.getSession().update(this.pedido.getEjecucion());
            }
            
            HibernateUtil.commitTransaction();
            return true;
        }
        catch(Exception e){
            HibernateUtil.rollbackTransaction();
            System.out.println("ERROR:"+e.getMessage()+"|");
            e.printStackTrace();
            return false;
        }
    }

    
    @Deprecated
    public Object agregarContactoResponsable(String nombreCR, int idRol, int idTipo, String tel) {
        ContactoResponsable cr = new ContactoResponsable();
        cr.setNombre(nombreCR);
        Telefono telCR = new Telefono();
        telCR.setNumero(tel);
        try {
            HibernateUtil.beginTransaction();
            cr.setRol((RolContactoResponsable) HibernateUtil.getSession().load(RolContactoResponsable.class,idRol));
            telCR.setTipo((TipoTelefono) HibernateUtil.getSession().load(TipoTelefono.class,idTipo));
            List telefonos = new ArrayList<Telefono>();
            telefonos.add(telCR);
            cr.setTelefonos(telefonos);
            this.contactos.add(cr);
            HibernateUtil.commitTransaction();
            return cr;

        } catch (Exception ex) {
            Logger.getLogger(GestorABMPedido.class.getName()).log(Level.SEVERE, null, ex);
            HibernateUtil.rollbackTransaction();
            return null;
        }
    }
    
    public Object agregarContactoResponsable(String nombreCR, String apellidoCR, int idRol, int idTipo, String tel) {
        ContactoResponsable cr = new ContactoResponsable();
        cr.setNombre(nombreCR);
        cr.setApellido(apellidoCR);
        Telefono telCR = new Telefono();
        telCR.setNumero(tel);
        try {
            HibernateUtil.beginTransaction();
            cr.setRol((RolContactoResponsable) HibernateUtil.getSession().load(RolContactoResponsable.class,idRol));
            telCR.setTipo((TipoTelefono) HibernateUtil.getSession().load(TipoTelefono.class,idTipo));
            List telefonos = new ArrayList<Telefono>();
            telefonos.add(telCR);
            cr.setTelefonos(telefonos);
            this.contactos.add(cr);
            HibernateUtil.commitTransaction();
            return cr;

        } catch (Exception ex) {
            Logger.getLogger(GestorABMPedido.class.getName()).log(Level.SEVERE, null, ex);
            HibernateUtil.rollbackTransaction();
            return null;
        }
    }

    /**
     * 
     * @return Un ArrayList con NTuplas. Estas contienen un array de objetos 
     * en el siguiente orden:
     *      [0] Nombre del Rol
     *      [1] Primer Teléfono
     *      [2] El Objeto ContactoResponsable
     */
    public ArrayList<NTupla> mostrarContactosResponsables(){
        ArrayList<NTupla> nTuplas = new ArrayList<NTupla>();

        Iterator iter = this.contactos.iterator();
        while ( iter.hasNext() )
        {
            ContactoResponsable cr = (ContactoResponsable)iter.next();
            NTupla  nt = new NTupla();
            nt.setNombre(cr.getNombre());
            Object datos[] = {cr.getRol().getNombre(),cr.getTelefonos().get(0),cr};
            nt.setData(datos);
            nTuplas.add(nt);
        }
        return nTuplas;
    }

    public boolean quitarContactoResponsable(Object o) {
        boolean r = this.contactos.remove(o);
        return r;
    }

    public void presupuestoMaximo(String text) {
        this.montoMaximo = Double.parseDouble(text);
    }

    public void plazoEntrega(String text) {
        this.plazoEntrega = text;
    }

    public void lugarEntrega(String text) {
        this.lugarEntrega = text;
    }

    public boolean agregarRolCR(String n) {
        RolContactoResponsable rcr = new RolContactoResponsable();
        rcr.setNombre(n);
        try {
            HibernateUtil.beginTransaction();
            HibernateUtil.getSession().save(rcr);
            HibernateUtil.commitTransaction();
            return true;
        } catch (Exception ex) {
            Logger.getLogger(GestorABMPedido.class.getName()).log(Level.SEVERE, null, ex);
            HibernateUtil.rollbackTransaction();
            return false;
        }
    }

    public double getMontoMaximo() {
        return montoMaximo;
    }

    public void setMontoMaximo(double montoMaximo) {
        this.montoMaximo = montoMaximo;
    }
    
    public double getIdFormaDePago()
    {
        return this.formaDePago.getId();
    }

    /**
     * Descarta todas las cotizaciones del Pedido de Obra.
     */
    private void darDeBajaCotizaciones() {
        if(this.pedido!=null){
            if(this.pedido.getCotizaciones()!=null){
                for (int i = 0; i < this.pedido.getCotizaciones().size(); i++) {
                    Cotizacion cot = this.pedido.getCotizaciones().get(i);
                    if(cot!=null){
                        cot.setEstadoDescartado();
                    }
                }
            }
        }
    }

    /**
     * Da de baja la planificacion Asociada al pedido de obra.
     */
    private void darDeBajaPlanificacion() {
        if(this.pedido!=null){
            if(this.pedido.getPlanificacion()!=null){
                this.pedido.getPlanificacion().setEstado(Planificacion.ESTADO_CANCELADA);
            }
        }
    }

    /**
     * Da de baja la ejecucion Asociada al pedido de obra.
     */
    private void darDeBajaEjecucion() {
        if(this.pedido!=null){
            if(this.pedido.getEjecucion()!=null){
                this.pedido.getEjecucion().setEstado(Ejecucion.ESTADO_CANCELADA);
            }
        }        
    }

    public void pliego(String pliego) {
        this.pliegoObra = pliego;
    }
}